feat: Introduce two-command local development setup (#962)#963
feat: Introduce two-command local development setup (#962)#963Lakshya-2440 wants to merge 18 commits intoalphaonelabs:mainfrom
Conversation
|
Note Reviews pausedIt looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the Use the following commands to manage reviews:
Use the checkboxes below for quick actions:
WalkthroughAdds a reproducible local development environment: Docker Compose (MySQL, Redis, Django), VS Code devcontainer, npm script wrappers, setup/dev/doctor shell scripts, CI onboarding smoke test, and related config (.gitignore, poetry.toml). Includes automation for dependency install, migrations, collectstatic, and health checks. Changes
Sequence Diagram(s)mermaid Dev->>Scripts: run Estimated code review effort🎯 4 (Complex) | ⏱️ ~45 minutes Suggested labels
🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Tip Try Coding Plans. Let us write the prompt for your AI agent so you can ship faster (with fewer bugs). Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 14
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Inline comments:
In @.devcontainer/devcontainer.json:
- Around line 1-8: The devcontainer.json contains JavaScript-style comments (//
and /* */) which make it JSONC and fail strict JSON checks; remove all comments
and any trailing commas so the file becomes valid JSON (replace commentary with
external docs or README), specifically strip occurrences of '//' and '/*...*/'
in .devcontainer/devcontainer.json and validate the result with a JSON
linter/check-json before committing.
In @.github/workflows/onboarding-smoke-test.yml:
- Around line 15-27: The workflow's push and pull_request "paths" lists are
missing .env.sample so changes to environment setup won't trigger the onboarding
smoke test; update the paths arrays under the push and pull_request sections in
the onboarding-smoke-test workflow to include '.env.sample' alongside
'scripts/**', 'package.json', 'pyproject.toml', 'poetry.lock', and
'.github/workflows/onboarding-smoke-test.yml' so any edits to the sample env
file will run the smoke test.
- Line 80: Update the unquoted kill invocations that use the SERVER_PID variable
so they use a quoted parameter: replace occurrences of kill $SERVER_PID
2>/dev/null || true with kill "${SERVER_PID}" 2>/dev/null || true (and similarly
for the other kill calls referencing SERVER_PID) to prevent word-splitting and
globbing issues.
- Around line 59-61: Remove the suppression of the exit code so real failures
from the onboarding check fail CI: keep the executable bit change for
scripts/doctor.sh but change the workflow step that runs "npm run doctor ||
true" to run "npm run doctor" (i.e., remove "|| true") so that the doctor
script's non-zero exit (failures) will fail the job; reference the "npm run
doctor" invocation and the "scripts/doctor.sh" executable change when making the
edit.
In @.gitignore:
- Line 16: The .gitignore currently lists "poetry.toml" but that file is now
committed and must be tracked; remove the "poetry.toml" entry from the
.gitignore so the repository consistently tracks the in-project Poetry config,
ensuring the committed poetry.toml continues to be versioned and shared with
collaborators (locate the "poetry.toml" line in .gitignore and delete it, then
commit the updated .gitignore).
In `@bash`:
- Around line 1-5: Remove the accidentally committed terminal output file named
"bash" from the repo, and in the setup script update the hardcoded Poetry
version string "1.8.3" to the current stable "2.3.2" (replace both occurrences
that pin Poetry); additionally, modify scripts/setup.sh to ensure compatibility
with Poetry 2.x by installing the poetry export plugin (poetry-plugin-export)
before any use of "poetry export" (or add conditional logic that installs the
plugin when POETRY_VERSION >= 2.0), and verify the export calls around the
existing "poetry export" usages still work (adjust fallback logic if the plugin
is missing).
In `@docker-compose.dev.yml`:
- Around line 20-22: The service is configured to provision a non-root DB user
(MYSQL_USER / MYSQL_PASSWORD) but the app's DATABASE_URL still uses the MySQL
root account; update the DATABASE_URL in docker-compose.dev.yml to use the
provisioned app credentials (MYSQL_USER and MYSQL_PASSWORD) and the service
hostname and database name instead of root, so the application runs with
least-privilege DB credentials (adjust any DATABASE_URL env or compose variable
references accordingly and remove hard-coded root:root usage).
In `@poetry.toml`:
- Around line 2-3: The poetry virtualenv settings are contradictory:
virtualenvs.create is false while virtualenvs.in-project is true, which prevents
creating a project-local .venv and triggers FileNotFoundError on fresh machines;
change virtualenvs.create to true so virtualenvs.in-project takes effect (i.e.,
set create = true alongside in-project = true) and ensure the virtualenvs.* keys
in poetry.toml (virtualenvs.create and virtualenvs.in-project) are consistent so
Poetry can create and register the project-local .venv.
In `@scripts/dev.sh`:
- Around line 60-61: The warning currently logs the raw REDIS_URL (variable
REDIS_URL) via the warn call, which may expose credentials; change the warn use
to log a redacted version instead by stripping any "username:password@" segment
before interpolation (e.g., remove everything between "://" and "@" or replace
with "://REDACTED@"), or alternatively parse and log only the host:port portion;
update the warn invocation(s) that reference REDIS_URL so they pass the
sanitized string rather than the raw variable.
- Around line 79-81: The script prints "Static files ready" even when
collectstatic fails because the collect step uses "${PYTHON}" manage.py
collectstatic --noinput --verbosity=0 2>&1 || true; remove the "|| true" so
failures propagate, and add an explicit check after the collect command (using
its exit status) to log an error (via the existing info/ok/err helpers) and exit
non‑zero if collectstatic failed; update the block around the "${PYTHON}"
manage.py collectstatic call and the subsequent ok "Static files ready" to only
run when the command succeeds.
In `@scripts/doctor.sh`:
- Line 42: The Python version check in scripts/doctor.sh currently requires
PY_MINOR >= 10 regardless of PY_MAJOR; update the conditional around the check
so it accepts any Python version with PY_MAJOR greater than 3 OR Python 3 with
PY_MINOR >= 10 (i.e., change the if that uses PY_MAJOR and PY_MINOR to implement
"PY_MAJOR > 3 OR (PY_MAJOR == 3 AND PY_MINOR >= 10)"), ensuring you adjust the
shell test operators and grouping accordingly so future major versions (e.g.,
4.x) pass.
- Line 25: The cd "${PROJECT_ROOT}" can fail silently; update scripts/doctor.sh
to explicitly handle failure after the cd (or enable shell exit-on-error) so the
script doesn't continue in the wrong directory—e.g., after the cd check its exit
status and log an error including PROJECT_ROOT and exit non‑zero if the cd fails
(reference the cd "${PROJECT_ROOT}" invocation and the PROJECT_ROOT variable).
In `@scripts/setup.sh`:
- Line 125: The script computes POETRY_CMD with a fallback but several calls
still invoke the hardcoded poetry binary (e.g., the commands at the spots that
currently run "poetry" such as the config call, install, and recovery commands);
update those to consistently use the resolved POETRY_CMD (or create a small
wrapper function like run_poetry() that invokes "${POETRY_CMD}" and use that) so
every invocation (previously hardcoded "poetry") uses ${POETRY_CMD} and will
work when the fallback path (python3 -m poetry) is required.
- Around line 220-221: The generated secret (NEW_SECRET) contains characters
like '&' which sed treats specially during substitution; before passing
NEW_SECRET into the sed replacement you must escape sed-special characters (at
minimum '&' and backslash, and any delimiter like '/' if used) so the
replacement inserts the literal secret. Modify the script to transform
NEW_SECRET into an escaped version (e.g., produce ESCAPED_SECRET by escaping &,
\, and the sed delimiter) and use ESCAPED_SECRET in the sed command that
replaces the placeholder, referencing the NEW_SECRET and sed replacement usage
in your script.
ℹ️ Review info
Configuration used: Organization UI
Review profile: ASSERTIVE
Plan: Pro
📒 Files selected for processing (12)
.devcontainer/devcontainer.json.github/workflows/onboarding-smoke-test.yml.gitignorealphaonelabs-education-website@1.0.0bashdocker-compose.dev.ymlpackage.jsonpoetry.tomlscripts/dev.shscripts/doctor.shscripts/setup.shweb/views.py
There was a problem hiding this comment.
Actionable comments posted: 6
♻️ Duplicate comments (3)
.github/workflows/onboarding-smoke-test.yml (2)
80-101:$SERVER_PIDis unquoted in all threekillinvocations.Lines 82, 96, and 101 reference
$SERVER_PIDwithout quoting, risking word-splitting if the variable is ever empty or multi-valued. Use"${SERVER_PID}"consistently.🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In @.github/workflows/onboarding-smoke-test.yml around lines 80 - 101, The three kill invocations use an unquoted $SERVER_PID which can cause word-splitting or errors if empty; update each occurrence of kill $SERVER_PID 2>/dev/null || true to use a quoted variable: kill "${SERVER_PID}" 2>/dev/null || true (preserve the redirection and the || true) so SERVER_PID is safely handled in the health-check and shutdown blocks.
60-63:|| truestill suppresses realdoctorfailures in CI.The
doctor.shscript already returns0for warnings and1for hard failures. Appending|| truesilences the non-zero exit that the script intentionally emits when something is broken, negating the regression-guard purpose of this step.🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In @.github/workflows/onboarding-smoke-test.yml around lines 60 - 63, The workflow step "Run doctor" currently appends "|| true" to the command which masks real failures from scripts/doctor.sh; update the run block to remove "|| true" so that "npm run doctor" can fail the job when scripts/doctor.sh returns non-zero (keep the "chmod +x scripts/doctor.sh" line and ensure the run command is simply "npm run doctor")..devcontainer/devcontainer.json (1)
1-38: The previously flagged comments (//) have been removed. The file is now valid strict JSON.🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In @.devcontainer/devcontainer.json around lines 1 - 38, Remove the stray "[duplicate_comment]" marker left in the review comment and confirm the devcontainer JSON contains no duplicate keys; specifically re-check entries like "postCreateCommand", "postStartCommand", "customizations.vscode.settings" and the "features" object to ensure there are no duplicated properties and the file remains strict JSON after the cleanup.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Inline comments:
In @.devcontainer/devcontainer.json:
- Around line 17-18: Remove the deprecated settings "python.linting.enabled" and
"python.linting.flake8Enabled" from the devcontainer settings block: locate the
entries with those keys in .devcontainer/devcontainer.json and delete them so
linting is handled by the ms-python.flake8 extension instead.
- Line 12: The postStartCommand in .devcontainer/devcontainer.json runs "python
manage.py migrate" immediately which can fail if MySQL isn't ready; update
postStartCommand to first wait for DB readiness (e.g., call a custom management
command like "python manage.py wait_for_db" or run a small wait loop that
attempts a DB connection) and only then run "python manage.py migrate --no-input
&& python manage.py collectstatic --noinput"; alternatively add a Docker Compose
healthcheck for the db service and use depends_on with service_healthy so the
container start is gated by DB readiness.
- Line 11: The postCreateCommand mutates the repo by running "poetry config
--local"; remove that invocation and instead set the POETRY_VIRTUALENVS_CREATE
environment variable to "false" in the command so Poetry behavior is configured
via env var and not by editing poetry.toml; update the "postCreateCommand" value
to something like prefixing the existing command with
POETRY_VIRTUALENVS_CREATE=false (keep pip install poetry==1.8.3 && poetry
install --no-interaction intact) so no local config is written.
In @.github/workflows/onboarding-smoke-test.yml:
- Around line 55-68: Workflow relies on running chmod +x on scripts/setup.sh,
scripts/doctor.sh and scripts/dev.sh in each step because those files were not
committed with the executable bit; fix by committing those scripts with execute
permission (use git update-index --chmod=+x for scripts/setup.sh
scripts/doctor.sh scripts/dev.sh or otherwise set the executable bit in your
repo) and then remove the redundant chmod +x lines from the
onboarding-smoke-test.yml steps so future script calls won’t depend on per-run
chmods.
- Around line 36-38: The CI job "smoke-test" currently has no timeout and
inherits GitHub's 6-hour default; add a timeout-minutes key under the smoke-test
job (e.g., timeout-minutes: 5) so the job declared as smoke-test will be
forcibly canceled if it runs longer than the expected ceiling; place the
timeout-minutes entry at the same indentation level as name and runs-on in the
smoke-test job definition.
- Around line 44-48: The workflow step using actions/setup-python@v5 named "Set
up Python 3.10" is configured with cache: "pip" but this repo uses Poetry;
update that step to use cache: "poetry" so Poetry's dependency cache is utilized
(replace the cache value in the actions/setup-python@v5 step).
---
Duplicate comments:
In @.devcontainer/devcontainer.json:
- Around line 1-38: Remove the stray "[duplicate_comment]" marker left in the
review comment and confirm the devcontainer JSON contains no duplicate keys;
specifically re-check entries like "postCreateCommand", "postStartCommand",
"customizations.vscode.settings" and the "features" object to ensure there are
no duplicated properties and the file remains strict JSON after the cleanup.
In @.github/workflows/onboarding-smoke-test.yml:
- Around line 80-101: The three kill invocations use an unquoted $SERVER_PID
which can cause word-splitting or errors if empty; update each occurrence of
kill $SERVER_PID 2>/dev/null || true to use a quoted variable: kill
"${SERVER_PID}" 2>/dev/null || true (preserve the redirection and the || true)
so SERVER_PID is safely handled in the health-check and shutdown blocks.
- Around line 60-63: The workflow step "Run doctor" currently appends "|| true"
to the command which masks real failures from scripts/doctor.sh; update the run
block to remove "|| true" so that "npm run doctor" can fail the job when
scripts/doctor.sh returns non-zero (keep the "chmod +x scripts/doctor.sh" line
and ensure the run command is simply "npm run doctor").
There was a problem hiding this comment.
Actionable comments posted: 4
♻️ Duplicate comments (2)
.github/workflows/onboarding-smoke-test.yml (1)
36-38:⚠️ Potential issue | 🟠 MajorAdd a
timeout-minutesceiling to prevent stalled runs from burning runner minutes.Without an explicit timeout, the job inherits GitHub Actions' 6-hour default. A smoke test expected to complete in a few minutes should enforce a ceiling.
Proposed fix
smoke-test: name: Setup & Boot runs-on: ubuntu-latest + timeout-minutes: 15🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In @.github/workflows/onboarding-smoke-test.yml around lines 36 - 38, The smoke-test job currently lacks a timeout so it can run up to the default 6 hours; add a timeout-minutes field to the smoke-test job (e.g., timeout-minutes: 10) in the workflow YAML under the smoke-test job definition to cap run time and prevent stalled runs from consuming runner minutes.scripts/setup.sh (1)
125-125:⚠️ Potential issue | 🔴 CriticalHardcoded
poetrycalls bypass the resolvedPOETRY_CMDfallback.Lines 125, 148, 160, 167, and 181 invoke
poetrydirectly instead of${POETRY_CMD}. If the fallback topython3 -m poetrywas triggered (lines 88–91), all these calls will fail with "command not found."Proposed fix (representative diff for all occurrences)
-poetry config virtualenvs.in-project true --local 2>/dev/null || true +${POETRY_CMD} config virtualenvs.in-project true --local 2>/dev/null || true-if poetry install --no-interaction --no-ansi 2>&1 | tail -5; then +if ${POETRY_CMD} install --no-interaction --no-ansi 2>&1 | tail -5; then- poetry export --without-hashes --no-interaction 2>/dev/null \ + ${POETRY_CMD} export --without-hashes --no-interaction 2>/dev/null \- poetry export --with dev --without-hashes --no-interaction 2>/dev/null \ + ${POETRY_CMD} export --with dev --without-hashes --no-interaction 2>/dev/null \- PYTHON="$(poetry env info -e 2>/dev/null || echo python3)" + PYTHON="$(${POETRY_CMD} env info -e 2>/dev/null || echo python3)"Also applies to: 148-148, 160-160, 167-167, 181-181
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@scripts/setup.sh` at line 125, Several invocations call the hardcoded literal "poetry" which bypasses the POETRY_CMD fallback; replace every direct "poetry" call with the POETRY_CMD variable (use "${POETRY_CMD}" or "${POETRY_CMD[@]}" as appropriate) so the script will work when the fallback sets POETRY_CMD="python3 -m poetry"; update the occurrences that currently read e.g. poetry config virtualenvs.in-project true, poetry install, poetry run, poetry build, etc., to use ${POETRY_CMD} in the same argument positions and preserve redirections and options.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Inline comments:
In @.github/workflows/onboarding-smoke-test.yml:
- Line 77: The shell test if [ $i -eq 30 ]; then is vulnerable to
word-splitting; update the test in the onboarding-smoke-test workflow to quote
the variable (i.e., use if [ "$i" -eq 30 ]; then) so the [ test command receives
a single token and avoids SC2086; locate the occurrence of the if statement
containing $i and replace it with the quoted form, ensuring any other similar
uses of $i in that script are also quoted consistently.
In `@scripts/setup.sh`:
- Line 81: The export line uses command substitution with dirname ("export
PATH=\"$(dirname \"${candidate}\"):${PATH}\"") which masks dirname's exit
status; instead, call dirname separately into a variable (e.g., dir=$(dirname
"${candidate}")), check its exit status and handle failure, then update PATH
using the variable (export PATH="${dir}:${PATH}"); reference the symbols
candidate, dirname, dir (or chosen var name), and PATH so you can locate and
replace the single-line export safely.
- Around line 255-264: The current sed commands unconditionally overwrite
ENVIRONMENT, DEBUG, and DATABASE_URL; change the logic to only apply defaults
when a variable is missing or set to a placeholder/empty value: for each of
ENVIRONMENT, DEBUG, and DATABASE_URL, first grep "${PROJECT_ROOT}/.env" for a
matching key; if not found, append "KEY=default" to the file; if found, read the
current value and only run the sed replacement when the value is empty or equals
a placeholder token (e.g., "" or "CHANGE_ME"); keep using PROJECT_ROOT and the
same variable names so the checks and conditional sed/append target ENVIRONMENT,
DEBUG, and DATABASE_URL without overwriting user-configured values.
- Around line 218-231: The sed-escape step for NEW_SECRET (produced in the
NEW_SECRET generation block) only escapes `/` and `&` but the subsequent sed
substitution for writing SECRET_KEY into ${PROJECT_ROOT}/.env uses `|` as the
delimiter, so you must also escape `|` (and ensure backslashes themselves are
escaped) when building ESCAPED_SECRET; update the ESCAPED_SECRET generation (the
printf | sed command that currently produces ESCAPED_SECRET) to escape
backslash, ampersand and pipe characters so the later sed calls that reference
ESCAPED_SECRET (both the darwin and non-darwin sed branches) cannot break when
the secret contains `|` or `\`.
---
Duplicate comments:
In @.github/workflows/onboarding-smoke-test.yml:
- Around line 36-38: The smoke-test job currently lacks a timeout so it can run
up to the default 6 hours; add a timeout-minutes field to the smoke-test job
(e.g., timeout-minutes: 10) in the workflow YAML under the smoke-test job
definition to cap run time and prevent stalled runs from consuming runner
minutes.
In `@scripts/setup.sh`:
- Line 125: Several invocations call the hardcoded literal "poetry" which
bypasses the POETRY_CMD fallback; replace every direct "poetry" call with the
POETRY_CMD variable (use "${POETRY_CMD}" or "${POETRY_CMD[@]}" as appropriate)
so the script will work when the fallback sets POETRY_CMD="python3 -m poetry";
update the occurrences that currently read e.g. poetry config
virtualenvs.in-project true, poetry install, poetry run, poetry build, etc., to
use ${POETRY_CMD} in the same argument positions and preserve redirections and
options.
There was a problem hiding this comment.
Actionable comments posted: 1
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Inline comments:
In `@scripts/dev.sh`:
- Around line 109-112: The current command pipes both stdout and stderr into
grep (using 2>&1), which can suppress important error messages; change the
redirection so only stdout is piped to grep and stderr is preserved (e.g.,
replace 2>&1 with 2> >(cat >&2) so manage.py runserver's stderr goes directly to
the terminal), and narrow the grep patterns in the existing regex (the long
alternation of messages) to be more specific if needed; look for the line with
"${PYTHON}" manage.py runserver 0.0.0.0:8000 2>&1 | grep --line-buffered -v -E
"^(Watching for file changes|Performing system checks|System check
identified|Django version|Starting development server|Quit the server with|$)"
and update the redirection and/or the regex there.
ℹ️ Review info
Configuration used: Organization UI
Review profile: ASSERTIVE
Plan: Pro
📒 Files selected for processing (6)
.gitignoredocker-compose.dev.ymlpoetry.tomlscripts/dev.shscripts/doctor.shscripts/setup.sh
| # Start Django dev server — filter out startup noise so the banner above | ||
| # stays as the last visible output. Request logs still pass through. | ||
| "${PYTHON}" manage.py runserver 0.0.0.0:8000 2>&1 \ | ||
| | grep --line-buffered -v -E "^(Watching for file changes|Performing system checks|System check identified|Django version|Starting development server|Quit the server with|$)" |
There was a problem hiding this comment.
🧹 Nitpick | 🔵 Trivial
Consider preserving stderr for debugging.
The grep filter removes Django startup messages but also pipes stderr through the same filter. If Django emits unexpected errors to stderr, they may be inadvertently suppressed.
♻️ Proposed refinement
-"${PYTHON}" manage.py runserver 0.0.0.0:8000 2>&1 \
- | grep --line-buffered -v -E "^(Watching for file changes|Performing system checks|System check identified|Django version|Starting development server|Quit the server with|$)"
+"${PYTHON}" manage.py runserver 0.0.0.0:8000 2>&1 \
+ | grep --line-buffered -v -E "^(Watching for file changes with StatReloader|Performing system checks\.\.\.|System check identified no issues|Django version [0-9]|Starting development server at|Quit the server with CONTROL-C\.|$)"
More specific patterns reduce the risk of filtering out unexpected error messages.
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.
In `@scripts/dev.sh` around lines 109 - 112, The current command pipes both stdout
and stderr into grep (using 2>&1), which can suppress important error messages;
change the redirection so only stdout is piped to grep and stderr is preserved
(e.g., replace 2>&1 with 2> >(cat >&2) so manage.py runserver's stderr goes
directly to the terminal), and narrow the grep patterns in the existing regex
(the long alternation of messages) to be more specific if needed; look for the
line with "${PYTHON}" manage.py runserver 0.0.0.0:8000 2>&1 | grep
--line-buffered -v -E "^(Watching for file changes|Performing system
checks|System check identified|Django version|Starting development server|Quit
the server with|$)" and update the redirection and/or the regex there.
💬 Unresolved Review ConversationsHi @Lakshya-2440! 👋 This pull request currently has 1 unresolved review conversation. Please address all review feedback and push a new commit to resolve them before this PR can be merged. Steps to resolve:
Once all conversations are resolved, this notice will be removed automatically. Thank you! 🙏 |
👀 Peer Review RequiredHi @Lakshya-2440! This pull request does not yet have a peer review. Before this PR can be merged, please request a review from one of your peers:
Thank you for contributing! 🎉 |
Lakshya-2440
left a comment
There was a problem hiding this comment.
I have fixed the linting error.
PR Title:
feat: Introduce two-command local development setup (#962)
PR Description:
Resolves #962
Description
This PR addresses issue #962 by introducing a standardized, two-command local development workflow. It drastically simplifies the onboarding process for new contributors by automating environment configuration, dependency installation, and database preparation.
Changes Made
scripts/setup.sh,scripts/dev.sh, andscripts/doctor.shto automate environment preparation, running, and diagnostics.npm run setup(viapackage.json) to safely duplicate.env.sample, generate secure secrets (SECRET_KEYandMESSAGE_ENCRYPTION_KEY), and apply development environment variables.manage.py create_test_data).sedcommands).web/views.py.onboarding-smoke-test.ymlGitHub Actions workflow to verify the setup process.How to Test
npm run setup.npm run devto start the development server.This ensures a reproducible sandbox environment across machines and reduces setup errors.
Summary by CodeRabbit
Chores
Refactor